package CarRentalSystem.costomer;

import CarRentalSystem.CarInfo.Bus;
import CarRentalSystem.CarInfo.Car;
import CarRentalSystem.CarInfo.Trunk;
import CarRentalSystem.CarInfo.Vehicle;
import CarRentalSystem.JDBCUtils.jdbcUtilsByAdmin;
import CarRentalSystem.RentMgrSys.RentMgrSys;
import CarRentalSystem.admin.admin;
import CarRentalSystem.menuMsg.menuMsg;
import java.sql.SQLException;
import java.util.ArrayList;

public abstract class User {
    private int userId=0;                          //用户ID
    private String identity = "";                  //身份信息，普通 or VIP
    private float money = 0;                       //账户余额
    private float discount;                        //享受的折扣
    static ArrayList<Car> myCar = new ArrayList<>();   //存储用户账户里已经租的车的信息
    static ArrayList<Bus> myBus = new ArrayList<>();
    static ArrayList<Trunk> myTrunk = new ArrayList<>();

    public final int rentCarLimitation;
    public int getUserId() {
        return userId;
    }

    public void setUserId(int userId) {
        this.userId = userId;
    }

    public String getIdentity() {
        return identity;
    }

    public void setIdentity(String identity) {
        this.identity = identity;
    }

    public float getMoney() {
        return money;
    }

    public void setMoney(float money) {
        this.money = money;
    }

    public double getDiscount() {
        return discount;
    }

    public void setDiscount(float discount) {
        this.discount = discount;
    }

    public void addMyVehicles(Vehicle v) {
        if (v instanceof Car){
            myCar.add((Car)v);
        } else if(v instanceof Bus){
            myBus.add((Bus)v);
        } else if(v instanceof Trunk){
            myTrunk.add((Trunk)v);
        }
    }

    public static void thisLoginDataClear(){
        if(myCar != null){
            myCar.clear();
        }
        if(myBus != null){
            myBus.clear();
        }
        if(myTrunk != null){
            myTrunk.clear();
        }
    }

    public User(int id, String identity, float money){
        setUserId(id);
        setIdentity(identity);
        setMoney(money);
        setDiscount((float)(identity.equals("VIP")?0.6:1.0));
        this.rentCarLimitation = identity.equals("VIP")?300:15;     //权限设置
    }

    //获取每类车的总数量
    public static int getEachKindCarTotalNum(ArrayList<? extends Vehicle> v){
        int nums=0;

        for (Vehicle vehicle : v) {
            nums += vehicle.getUserRentNum();
        }

        return nums;
    }

    //获取当前某个车辆的库存
    public static int hasThisKindCar(int id){
        int res = 0;

        String sql = "select nums from cardata where id="+id;
        try {
            RentMgrSys.rs = RentMgrSys.stmt.executeQuery(sql);
            if(RentMgrSys.rs.next()){
                res = RentMgrSys.rs.getInt("nums");
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }

        return res;
    }

    public static void PayOrNot(User user, float money, float rent,  Vehicle car){
        if(money >= rent){
            jdbcUtilsByAdmin.UpdateMoney(rent, user.getUserId());
            user.setMoney(user.getMoney() - rent); //用户付款
            user.addMyVehicles(car);
            System.out.println("租车成功！付款"+rent+"元， 当前账户余额: "+user.getMoney()+"元\n");
            jdbcUtilsByAdmin.UpdateMoney(rent, 0); //后台到账
        }else{
            menuMsg.moneyNotEnough();

            if(user instanceof ordinaryAboutCostomer){
                ((ordinaryAboutCostomer) user).userMenu();
            }else if(user instanceof VIPAboutCostomer){
                ((VIPAboutCostomer) user).userMenu();
            }
        }
    }

    //还车
    public static void returnCar(){

    }

    //租车部分
    public static int rentWhichCar(User user, int id, int rentSum){
        System.out.println("请输入您需要租的数量、租用的天数: ");
        int carNum = RentMgrSys.in.nextInt();
        int days = RentMgrSys.in.nextInt();

        if(carNum <= 0){//不租
            return 0;
        }else if(rentSum+carNum <= user.rentCarLimitation){
            int hasCar = hasThisKindCar(id);
            //System.out.println(hasCar);
            if(carNum > hasCar){
                System.out.println("公司闲置的当前款式车辆不足, 无法出租, 请选择其他款式车辆");
            }else{
                try {
                    RentMgrSys.stmt.executeUpdate(jdbcUtilsByAdmin.sqlChangeCarSpecifyInfo(id, "nums", hasCar-carNum)); //修改数据库中的车辆数据
                    RentMgrSys.rs = RentMgrSys.stmt.executeQuery(jdbcUtilsByAdmin.sqlSearchCarSpecifyInfo("*", id));                         //读取数据库中所选车辆的所有信息
                    if(RentMgrSys.rs.next()){
                        //提取读取到的信息
                        String v = RentMgrSys.rs.getString("vehicle");
                        String b = RentMgrSys.rs.getString("brand");
                        String type = RentMgrSys.rs.getString("type");
                        int pr = RentMgrSys.rs.getInt("preRent");
                        int features;
                        float rent;
                        switch (v) {
                            case "轿车":
                                features = -1;
                                Vehicle car = new Car(v, b, type, pr, carNum, features);
                                rent = car.calRent(carNum * days, user);
                                PayOrNot(user, user.getMoney(), rent, car);
                                RentMgrSys.stmt.executeUpdate(jdbcUtilsByAdmin.sqlAddCarInfoIntoUserOwnCar(user.getUserId(), v, b, type, carNum));
                                break;
                            case "客车": {
                                System.out.print("请输入您的乘客数量: ");
                                features = RentMgrSys.in.nextInt();
                                int limit = RentMgrSys.rs.getInt("feature");
                                int realNums = (int) Math.ceil(features * 1.0 / limit);
                                System.out.println(realNums);

                                if (realNums != carNum) {
                                    //stock = realNums;
                                    System.out.println("客户您好，根据您的乘客数量以及选择的车型，系统自动为您进行了调整~本车型您实际租车数量为: " + realNums);
                                    //库存不足，则自动补货
                                    if (realNums > hasCar) {
                                        admin.relenishment(id, realNums - hasCar);
                                        System.out.println("该款车型存量不足，正在为您补货，请稍后再进行租赁~");
                                    } else {
                                        carNum = realNums;
                                        Vehicle bus = new Bus(v, b, type, pr, carNum, features);
                                        rent = bus.calRent(carNum * days, user);
                                        PayOrNot(user, user.getMoney(), rent, bus);
                                        RentMgrSys.stmt.executeUpdate(jdbcUtilsByAdmin.sqlAddCarInfoIntoUserOwnCar(user.getUserId(), v, b, type, carNum));
                                    }
                                } else {
                                    Vehicle bus = new Bus(v, b, type, pr, carNum, features);
                                    rent = bus.calRent(carNum * days, user);
                                    PayOrNot(user, user.getMoney(), rent, bus);
                                    RentMgrSys.stmt.executeUpdate(jdbcUtilsByAdmin.sqlAddCarInfoIntoUserOwnCar(user.getUserId(), v, b, type, carNum));
                                }
                                break;
                            }
                            case "货车": {
                                System.out.println("\n     货车计重收费标准如下\n     1、装载10t内: 每吨每公里收费0.08元\n     2、装载超过10t但不超过40t: 超过部分每吨每公里加收0.04元\n     3、装载超过40t但未超过上限: 超过40t的部分每吨每公里再加收0.08元\n");
                                System.out.println("请输入您的货物重量(不足 1t 的部分记为 0t): ");
                                features = RentMgrSys.in.nextInt();
                                int limit = RentMgrSys.rs.getInt("feature");
                                int realNums = (int) Math.ceil(features * 1.0 / limit);

                                if (realNums != carNum) {
                                    System.out.println("客户您好，根据您的货物重量以及选择的车型，系统自动为您分配了合适的安排~本车型您实际租车数量为: " + realNums);

                                    if (realNums > hasCar) {
                                        admin.relenishment(id, realNums - hasCar);
                                        System.out.println("该款车型存量不足，正在为您补货，请稍后再进行租赁~");
                                    } else {
                                        carNum = realNums;
                                        Vehicle trunk = new Trunk(v, b, type, pr, carNum, features);
                                        rent = trunk.calRent(carNum * days, user);
                                        PayOrNot(user, user.getMoney(), rent, trunk);
                                        RentMgrSys.stmt.executeUpdate(jdbcUtilsByAdmin.sqlAddCarInfoIntoUserOwnCar(user.getUserId(), v, b, type, carNum));
                                    }
                                } else {
                                    Vehicle trunk = new Trunk(v, b, type, pr, carNum, features);
                                    rent = trunk.calRent(carNum * days, user);
                                    PayOrNot(user, user.getMoney(), rent, trunk);
                                    RentMgrSys.stmt.executeUpdate(jdbcUtilsByAdmin.sqlAddCarInfoIntoUserOwnCar(user.getUserId(), v, b, type, carNum));
                                }
                                break;
                            }
                        }

                        rentSum += carNum;
                    }
                } catch (SQLException e) {
                    e.printStackTrace();
                }

            }
        } else if (rentSum+carNum > user.rentCarLimitation) {
            System.out.println("您当前的账户仓库中, 租车上限为"+user.rentCarLimitation+"辆, 请重新选择您的租车数目, 或是先归还已租出的车辆, 或是升级为VIP客服提升上限至300");
        }


        return rentSum;
    }

    /**
     * 登录账号的租车信息与数据库同步
     * @return 无
     * */
    //登录时创建几个集合，用于从数据里提取登录的用户账号中，用户正在租用的车辆，将其分类入集合中
    //此操作在登录成功后, 登录用户对象创建完成后才会进行

    public void everyKindCarSync(User user, String carKind){
        try {
            RentMgrSys.rs = RentMgrSys.stmt.executeQuery(jdbcUtilsByAdmin.sqlReadUserSpecificKindWhichCarInfo(carKind, user.getUserId()));
            RentMgrSys.rs.last();
            int row = RentMgrSys.rs.getRow();
            RentMgrSys.rs.absolute(1);

            if(row == 0) {
                return;
            }


            String vehicle="";
            String brand="";
            String type="";
            int nums=0;

            do{
                vehicle = RentMgrSys.rs.getString("vehicle");
                brand = RentMgrSys.rs.getString("brand");
                type = RentMgrSys.rs.getString("type");
                nums = RentMgrSys.rs.getInt("nums");

                switch (carKind) {
                    case "轿车":
                        //车的日租金和特征值都设为-1，表示这里不使用
                        Vehicle car = new Car(vehicle, brand, type, -1, nums, -1);
                        user.addMyVehicles(car);
                        break;
                    case "客车":
                        Vehicle bus = new Bus(vehicle, brand, type, -1, nums, -1);
                        user.addMyVehicles(bus);
                        break;
                    case "货车":
                        Vehicle trunk = new Trunk(vehicle, brand, type, -1, nums, -1);
                        user.addMyVehicles(trunk);
                        break;
                }
            }while(RentMgrSys.rs.next());

        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    public void myCarDataSync(User user){
        try {
            //从数据库中获取登录用户车辆的信息
            RentMgrSys.rs = RentMgrSys.stmt.executeQuery(jdbcUtilsByAdmin.sqlReadSpecifyUserRentCarsInfo("*", user.getUserId()));
            RentMgrSys.rs.last();              //游标放到最后一行获取
            int row = RentMgrSys.rs.getRow();  //获取行数
            if(row == 0){
                return;
            }else{
                user.everyKindCarSync(this, "轿车");
                user.everyKindCarSync(this, "客车");
                user.everyKindCarSync(this, "货车");
            }

        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

}
